package com.lizicloud.user.userLogin.service;

import com.lizicloud.application.dto.ApiResponse;
import com.lizicloud.user.userLogin.constants.LoginConstants;
import com.lizicloud.user.userLogin.dto.LoginDTO;
import com.lizicloud.user.userLogin.dto.LoginResponse;
import com.lizicloud.domain.model.User;
import com.lizicloud.infrastructure.common.utils.JwtUtils;
import com.lizicloud.infrastructure.persistence.UserMapper;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import jakarta.servlet.http.HttpServletRequest;
import java.time.LocalDateTime;

/**
 * 用户服务类
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class UserService {
    
    private final UserMapper userMapper;
    private final JwtUtils jwtUtils;
    private final PasswordEncoder passwordEncoder;
    
    /**
     * 用户登录
     */
    @Transactional
    public ApiResponse<LoginResponse> login(LoginDTO loginDTO, HttpServletRequest request) {
        try {
            // 根据用户账号查询用户
            User user = userMapper.selectByUseraccount(loginDTO.getUseraccount());
            
            // 验证用户是否存在
            if (user == null) {
                return ApiResponse.error(LoginConstants.INVALID_CREDENTIALS_MESSAGE);
            }
            
            // 验证用户状态
            if (user.getStatus() == LoginConstants.USER_STATUS_DISABLED) {
                return ApiResponse.error(LoginConstants.USER_DISABLED_MESSAGE);
            }
            
            // 添加调试日志
            log.debug("Login attempt for user: {}", loginDTO.getUseraccount());
            log.debug("Received password: {}, length: {}", loginDTO.getPassword().substring(0, Math.min(2, loginDTO.getPassword().length())) + "...", loginDTO.getPassword().length());
            log.debug("Stored password: {}, length: {}, startsWith $2a$: {}", 
                user.getPassword().substring(0, Math.min(10, user.getPassword().length())) + "...", 
                user.getPassword().length(), 
                user.getPassword().startsWith("$2a$"));
            
            // 验证密码
            if (!passwordEncoder.matches(loginDTO.getPassword(), user.getPassword())) {
                log.debug("Password mismatch for user: {}", loginDTO.getUseraccount());
                return ApiResponse.error(LoginConstants.INVALID_CREDENTIALS_MESSAGE);
            }
            
            // 生成JWT令牌
            String token = jwtUtils.generateToken(
                user.getUseraccount(), 
                user.getId(), 
                user.getRole()
            );
            
            // 更新用户登录信息
            String loginIp = getClientIp(request);
            userMapper.updateLoginInfo(user.getId(), LocalDateTime.now(), loginIp);
            
            // 构建响应数据
            LoginResponse.UserInfo userInfo = new LoginResponse.UserInfo(
                user.getId(),
                user.getUsername(),
                user.getRole(),
                user.getAvatar()
            );
            
            LoginResponse loginResponse = new LoginResponse(
                token,
                LoginConstants.TOKEN_TYPE,
                userInfo
            );
            
            log.info(LoginConstants.LOGIN_SUCCESS_LOG, loginDTO.getUseraccount());
            return ApiResponse.success(loginResponse);
        } catch (Exception e) {
            log.error(LoginConstants.LOGIN_FAILURE_LOG, loginDTO.getUseraccount(), e.getMessage());
            return ApiResponse.error(LoginConstants.LOGIN_FAILURE_MESSAGE);
        }
    }
    
    /**
     * 获取用户信息
     */
    public ApiResponse<LoginResponse.UserInfo> getUserInfo(String useraccount) {
        try {
            User user = userMapper.selectByUseraccount(useraccount);
            if (user == null) {
                return ApiResponse.error(LoginConstants.USER_NOT_FOUND_MESSAGE);
            }
            
            LoginResponse.UserInfo userInfo = new LoginResponse.UserInfo(
                user.getId(),
                user.getUsername(),
                user.getRole(),
                user.getAvatar()
            );
            
            return ApiResponse.success(userInfo);
            
        } catch (Exception e) {
            log.error(LoginConstants.GET_USER_INFO_FAILURE_LOG, useraccount, e.getMessage());
            return ApiResponse.error(LoginConstants.GET_USER_INFO_FAILURE_MESSAGE);
        }
    }
    
    /**
     * 获取客户端IP地址
     */
    private String getClientIp(HttpServletRequest request) {
        String ip = request.getHeader("X-Forwarded-For");
        if (ip == null || ip.isEmpty() || LoginConstants.UNKNOWN_IP.equalsIgnoreCase(ip)) {
            ip = request.getHeader("Proxy-Client-IP");
        }
        if (ip == null || ip.isEmpty() || LoginConstants.UNKNOWN_IP.equalsIgnoreCase(ip)) {
            ip = request.getHeader("WL-Proxy-Client-IP");
        }
        if (ip == null || ip.isEmpty() || LoginConstants.UNKNOWN_IP.equalsIgnoreCase(ip)) {
            ip = request.getHeader("HTTP_CLIENT_IP");
        }
        if (ip == null || ip.isEmpty() || LoginConstants.UNKNOWN_IP.equalsIgnoreCase(ip)) {
            ip = request.getHeader("HTTP_X_FORWARDED_FOR");
        }
        if (ip == null || ip.isEmpty() || LoginConstants.UNKNOWN_IP.equalsIgnoreCase(ip)) {
            ip = request.getRemoteAddr();
        }
        
        // 如果是多级代理，取第一个IP
        if (ip != null && ip.contains(",")) {
            ip = ip.substring(0, ip.indexOf(",")).trim();
        }
        
        return ip;
    }
}